//
// Created by jinling on 2025/6/25.
//
#include "FileLogMgr.h"

#include "StringUtils.h"
#include "TTime.h"
#include <iostream>
using namespace tmms::base;

namespace
{
    static  tmms::base::FileLogPter file_log_nullpter;//这种写法主要用于实现内部链接（Internal Linkage），确保该变量的作用域局限于当前文件。
}


void FileLogMgr::OnCheck()  
{
    std::cout<<"ispesting!"<<std::endl;
    bool day_change{false};
    bool hour_change{false};
    int year=0,month=0,day =0 ,hour=0,minute=0,second=0;
    TTime::Now(year,month,day,hour,minute,second); //获取当前时间
    if (last_day_ ==-1)
    {
        last_day_ = day;
        last_hour_= hour;
    }
    if (last_day_ != day )
    {
        day_change = true;
    }
    if (last_hour_ != hour )
    {
        hour_change = true;
    }
    if (!day_change && !hour_change) //时间还没到，不用滚动
    {
       return ;
    }
    std::lock_guard<std::mutex> lk(lock_);
    for (auto &l :logs_) //时间到了的或，这个容器内的所有文件都点得滚动了
    {
        if (hour_change&&l.second->GetRotateType()==kRotateHour)
        {
            RotateHours(l.second);
        }
        if (day_change&&l.second->GetRotateType()==kRotateDay)
        {
            RotateDays(l.second);
        }
    }
    last_day_= day;
    last_hour_ = hour;
    last_month_ =month;
    last_year_ = year;
}


FileLogPter FileLogMgr::GetFileLog(const std::string &file_name) 
//查找这个日志文件有没有创建，是：返回这个文件 否：新建这个文件，加入map并将他返回：：
//写文件使用的时候 可以直接这样输入： FileLogMgr->GetFileLog("filename")->WriteLog("hello brother ,this is the messsge which is going to be woten into the file named 'filename'")
//但是这个文件一般是用来滚动日志文件的，不应该用来写日志文件，用LogStream来写会有DEBUG INFO这样的提醒  我觉得还好
{
    std::lock_guard<std::mutex> lk(lock_);
    auto iter = logs_.find(file_name);
    if (iter != logs_.end())
    {
        return iter->second;
    }
    FileLogPter log =std::make_shared<FileLog>(); //新打开一个
    if (!log->Open(file_name))
    {
        return file_log_nullpter;
    }
    logs_.emplace(file_name,log); //加进去
    return log;
}


void FileLogMgr::RemoveFileLog(const FileLogPter &log)
{
    std::lock_guard<std::mutex> lk(lock_);
    logs_.erase(log->FilePath());
}

void FileLogMgr::RotateDays(const FileLogPter &file) //进行文件滚动，这里主要是把当前时间，传入flilog进行文件滚动，已完成他的命名
{
    if (file->FileSize()<0)
    {
        char buf[128] = {0 };
        sprintf(buf,"_%04d-%02d-%02d",last_year_,last_month_,last_day_); //格式
        std::string file_path = file->FilePath();
        std::string path = StringUtils::FilePath(file_path); //之前定义的string操作函数：从路径中取得文件名
        std::string file_name = StringUtils::FileName(file_path);
        std::string file_ext=StringUtils::Extension(file_path);

        std::ostringstream ss;
        ss<<path<<file_name<<buf<<file_ext;
        file->Rotate(ss.str());
    }
}

void FileLogMgr::RotateHours(const FileLogPter &file)
{
    if (file->FileSize()<0)
    {
        char buf[128] = {0};
        sprintf(buf,"_%04d-%02d-%02dT%02d",last_year_,last_month_,last_day_,last_hour_); //格式
        std::string file_path = file->FilePath();
        std::string path = StringUtils::FilePath(file_path); //之前定义的string操作函数：从路径中取得文件名
        std::string file_name = StringUtils::FileName(file_path);
        std::string file_ext=StringUtils::Extension(file_path);
        std::ostringstream ss;
        ss<<path<<file_name<<buf<<file_ext;
        file->Rotate(ss.str());
    }
}